#include <ctime>
#include "Task.hpp"
#include "BlockQueue.hpp"

using std::cout;
using std::endl;

int Add(int x, int y) { return x + y; } // 定义一个函数

void *consumer(void *args) // 消费者
{
    BlockQueue<Task> *block_queue = (BlockQueue<Task> *)args;

    while (true)
    { // 拿出任务
        Task t;
        block_queue->pop(t); // 拿出了任务

        // 执行任务
        int sum = t(); // 得到结果
        cout << "消费者[" << pthread_self() << "]: " << t._x << " + " << t._y << " = " << sum << endl;

        sleep(1);
    }
}

void *productor(void *args) // 生产者
{
    BlockQueue<Task> *block_queue = (BlockQueue<Task> *)args;

    while (true)
    {
        // 制作任务
        int x = rand() % 100;
        int y = rand() % 200;
        Task t(x, y, Add);

        // 生产任务
        block_queue->push(t);

        cout << "生产者[" << pthread_self() << "]: " << x << " + " << y << " = ?" << endl;
        sleep(1);
    }

    return nullptr;
}

int main()
{
    srand((uint64_t)time(nullptr) ^ 0x56523); // 让产生的随机数更随机

    pthread_t c[2], p[2]; // 生产者和消费者个创建两个对象

    // 任务队列一定是全局的,因为生产者和消费者都是从这个阻塞队列中放入和拿取数据的
    BlockQueue<Task> *block_queue = new BlockQueue<Task>;

    pthread_create(c, nullptr, consumer, (void *)block_queue);
    pthread_create(c + 1, nullptr, consumer, (void *)block_queue);
    pthread_create(p, nullptr, productor, (void *)block_queue);
    pthread_create(p + 1, nullptr, productor, (void *)block_queue);

    pthread_join(c[0], nullptr);
    pthread_join(c[1], nullptr);
    pthread_join(p[0], nullptr);
    pthread_join(p[1], nullptr);
    return 0;
}